package com.google.gwt.sample.dynatablerf.client.presenters;

import java.util.ArrayList;
import java.util.List;
import java.util.Set;

import com.google.gwt.event.logical.shared.SelectionEvent;
import com.google.gwt.event.shared.EventBus;
import com.google.gwt.sample.dynatablerf.client.events.CloseMaterialListEvent;
import com.google.gwt.sample.dynatablerf.client.events.MaterialSelectionChangeEvent;
import com.google.gwt.sample.dynatablerf.shared.GrifoRequestFactory;
import com.google.gwt.sample.dynatablerf.shared.GrifoRequestFactory.MaterialProjetoRequest;
import com.google.gwt.sample.dynatablerf.shared.GrifoSharedConstants;
import com.google.gwt.sample.dynatablerf.shared.GrifoSharedConvertUtil;
import com.google.gwt.sample.dynatablerf.shared.MaterialProjetoProxy;
import com.google.gwt.sample.dynatablerf.shared.MaterialProjetoQueryParamsProxy;
import com.google.gwt.sample.dynatablerf.shared.MaterialProxy;
import com.google.gwt.sample.dynatablerf.shared.ProjetoProxy;
import com.google.gwt.user.client.ui.MultiWordSuggestOracle.MultiWordSuggestion;
import com.google.gwt.user.client.ui.SuggestOracle;
import com.google.gwt.user.client.ui.SuggestOracle.Callback;
import com.google.gwt.user.client.ui.SuggestOracle.Request;
import com.google.gwt.user.client.ui.SuggestOracle.Response;
import com.google.gwt.user.client.ui.SuggestOracle.Suggestion;
import com.google.web.bindery.requestfactory.shared.Receiver;

public class MaterialProjetoListPresenter
		extends
		MultipleSelectionDataPresenter<MaterialProjetoProxy, MaterialProjetoRequest> {

	class MaterialWordSuggestion extends MultiWordSuggestion {

		private MaterialProxy materialProxy;

		public MaterialWordSuggestion(MaterialProxy materialProxy) {
			super("", materialProxy.getCodigoMaterial() + " - "
					+ materialProxy.getDescricao());
			this.materialProxy = materialProxy;
		}

		public MaterialProxy getMaterialProxy() {
			return materialProxy;
		}

	}

	private MultipleSelectionDataDisplay<MaterialProjetoProxy> display;
	private ProjetoProxy projetoProxy;
	private int numMaterialProjeto;

	public MaterialProjetoListPresenter(
			MultipleSelectionDataDisplay<MaterialProjetoProxy> display,
			ProjetoProxy projetoProxy, GrifoRequestFactory requestFactory,
			EventBus eventBus) {
		super(eventBus, requestFactory);
		this.display = display;
		this.projetoProxy = projetoProxy;
	}

	@Override
	protected MultipleSelectionDataDisplay<MaterialProjetoProxy> getMultipleSelectionDataDisplay() {
		return display;
	}

	@Override
	protected void onMultipleSelection(Set<MaterialProjetoProxy> selectedSet) {
		getEventBus().fireEvent(
				new MaterialSelectionChangeEvent(selectedSet, projetoProxy));

	}

	@Override
	protected void fetch(final int start, int length) {
		MaterialProjetoRequest materialProjetoRequest = getRequestContext();

		MaterialProjetoQueryParamsProxy paramsProxy = materialProjetoRequest
				.create(MaterialProjetoQueryParamsProxy.class);
		paramsProxy.setProjeto(projetoProxy);

		materialProjetoRequest.findAll(paramsProxy, start, length)
				.with("material")
				.fire(new Receiver<List<MaterialProjetoProxy>>() {

					@Override
					public void onSuccess(List<MaterialProjetoProxy> response) {
						if (response.isEmpty()) {
							getAsyncDataProvider().updateRowCount(0, true);

						} else {
							getAsyncDataProvider().updateRowCount(
									numMaterialProjeto, true);

						}
						getAsyncDataProvider().updateRowData(start, response);
					}
				});

	}

	@Override
	protected void fireCloseWindowEvent() {
		getEventBus().fireEvent(new CloseMaterialListEvent(projetoProxy));

	}

	@Override
	protected void fetch() {

		MaterialProjetoRequest materialProjetoRequest = getRequestContext();

		MaterialProjetoQueryParamsProxy paramsProxy = materialProjetoRequest
				.create(MaterialProjetoQueryParamsProxy.class);

		paramsProxy.setProjeto(projetoProxy);

		materialProjetoRequest.count(paramsProxy).fire(new Receiver<Long>() {

			@Override
			public void onSuccess(Long response) {
				numMaterialProjeto = GrifoSharedConvertUtil
						.converToInteger(response);

			}
		});

	}

	@Override
	protected void fetchSuggestions(final Request request,
			final Callback callback) {

		MaterialProjetoRequest materialProjetoRequest = getRequestContext();

		MaterialProjetoQueryParamsProxy paramsProxy = materialProjetoRequest
				.create(MaterialProjetoQueryParamsProxy.class);
		paramsProxy.setProjeto(projetoProxy);

		materialProjetoRequest
				.findAll(request.getQuery(), paramsProxy,
						GrifoSharedConstants.SUGGESTION_MAX_RESULT)
				.with("material")
				.fire(new Receiver<List<MaterialProjetoProxy>>() {

					@Override
					public void onSuccess(List<MaterialProjetoProxy> response) {

						List<Suggestion> suggestions = new ArrayList<SuggestOracle.Suggestion>();
						if (response != null) {
							for (MaterialProjetoProxy materialProjetoProxy : response) {
								suggestions.add(new MaterialWordSuggestion(
										materialProjetoProxy.getMaterial()));
							}
						}
						callback.onSuggestionsReady(request, new Response(
								suggestions));
					}
				});

	}

	@Override
	protected void onFetchSelection(SelectionEvent<Suggestion> event) {
		// TODO Auto-generated method stub

	}

	@Override
	protected MaterialProjetoRequest getRequestContext() {
		return getRequestFactory().materialProjetoRequest();
	}
	
}